﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Text;
using GlobalHelper;

namespace _827Cycle
{
    public class BusCycle
    {
        DataTable _minset = new DataTable();

        public BusCycle(int tokenNumber)
        {
            _minset = Helper.CreateEmptyDataTableWithString(1, tokenNumber);

            //初始化最小集内容, 默认总是1号元初始绑定1号路牌
            for (int i = 0; i < _minset.Columns.Count; i++)
            {
                _minset.Rows[i][0] = i + 1;
            }
        }

        /// <summary>
        /// 轮转组,轮转
        /// </summary>
        /// <param name="cycleDirction"></param>
        public DataTable DoCycle(bool cycleDirction)
        {
            if (_minset.Columns.Count < 1 || _minset.Rows.Count < 1)
            {
                return null;
            }

            DataTable result = new DataTable(); 

            #region get value

            int col = _minset.Columns.Count - 1;
            IList<string> workArea = new List<string>();
            IList<string> firstCol = new List<string>();

            //first col
            for (int i = 0; i < _minset.Rows.Count; i++)
            {
                firstCol.Add(_minset.Rows[i][0].ToString());
            }

            //current col
            for (int i = 0; i < _minset.Rows.Count; i++)
            {
                workArea.Add(_minset.Rows[i][col].ToString());
            }

            #endregion

            #region do cycle

            //set firstCol
            for (int i = 0; i < _minset.Rows.Count; i++)
            {
                _minset.Rows[i][0] = firstCol[i];
            }

            //cycle
            IList<string> temp;

            do
            {
                temp = DoCycle(workArea, cycleDirction);
                _minset = SetCol(_minset, temp);

            } while (IsFinished(firstCol, temp));

            #endregion

            return result;

        }

        /// <summary>
        /// 在一个DataTable,加入指定内容在最后一列
        /// </summary>
        /// <param name="dt"></param>
        /// <param name="list"></param>
        /// <returns></returns>
        private static DataTable SetCol(DataTable dt,IList<string> list)
        {
            if (list.Count <= 0)
            {
                return null;
            }
            
            if (dt.Columns.Count != list.Count)
            {
                return null;
            }

            DataTable result = dt;

            result = Helper.AddNewColWithString(result);


            int col = result.Columns.Count - 1;
            for (int i = 0; i < result.Columns.Count; i++)
            {
                result.Rows[i][col] = list[i];
            }

            return result;
        }

        /// <summary>
        /// 判断, 2个string数组是否完全相同
        /// </summary>
        /// <param name="list1"></param>
        /// <param name="list2"></param>
        /// <returns></returns>
        private static bool IsFinished(IList<string> list1, IList<string> list2)
        {
            if (list1.Count <= 0 || list2.Count <= 0)
            {
                return false;
            }
            if (list1.Count != list2.Count)
            {
                return false;
            }

            bool result = true;

            for (int i = 0; i < list1.Count; i++)
            {
                if (list1[i] != list2[i])
                {
                    result = false;
                    break;
                }
            }

            return result;
        }

        /// <summary>
        /// 数组,轮转
        /// </summary>
        /// <param name="list"></param>
        /// <param name="cycleDirction"></param>
        /// <returns></returns>
        private static IList<string> DoCycle(IList<string> list, bool cycleDirction)
        {
            if (list.Count <= 0)
            {
                return null;
            }

            var result = list;

            string temp = string.Empty;

            if (cycleDirction)
            {
                //正向, 所有元下移 , 最后一个放第一个
                temp = result[result.Count - 1];

                for (int i = result.Count - 1; i > 0; i--)
                {
                    result[i] = result[i - 1];
                }

                result[0] = temp;
            }
            else
            {
                //反向, 所有元上移,第一个放最后一个
                temp = result[0];

                for (int i = 0; i < result.Count - 1; i++)
                {
                    result[i] = result[i + 1];
                }

                result[result.Count - 1] = temp;
            }

            return result;
        }
    }
}
